﻿using Microsoft.AspNetCore.Mvc.ApiExplorer;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Options;
using Microsoft.OpenApi.Models;
using Swashbuckle.AspNetCore.Filters;
using Swashbuckle.AspNetCore.SwaggerGen;
using System;
using System.Collections.Generic;
using System.IO;
using System.Reflection;
using System.Text;

namespace BJoin.Application.WebApi.Swagger
{
    public class SetupSwaggerOptions : IConfigureOptions<SwaggerGenOptions>
    {
        readonly IApiVersionDescriptionProvider _provider;
        readonly ILogger<SetupSwaggerOptions> _logger;

        public SetupSwaggerOptions(ILogger<SetupSwaggerOptions> logger, IApiVersionDescriptionProvider provider)
        {
            _logger = logger;
            _provider = provider;
        }

        public void Configure(SwaggerGenOptions options)
        {
            var c = options;
            c.OrderActionsBy((apiDesc) => $"{apiDesc.ActionDescriptor.RouteValues["controller"]}_{apiDesc.HttpMethod}");
            c.EnableAnnotations();
            var xmlFile = $"{Assembly.GetEntryAssembly().GetName().Name}.xml";
            var xmlPath = Path.Combine(AppContext.BaseDirectory, xmlFile);
            if (File.Exists(xmlPath))
                c.IncludeXmlComments(xmlPath, true);
            else
                _logger.LogWarning($"the '{xmlPath}' not exist.");
            xmlPath = Path.Combine(AppContext.BaseDirectory, "BJoin.Application.BObject.xml");
            if (File.Exists(xmlPath))
                c.IncludeXmlComments(xmlPath, true);
            else
                _logger.LogWarning($"the '{xmlPath}' not exist.");
            xmlPath = Path.Combine(AppContext.BaseDirectory, "BJoin.Application.Dto.xml");
            if (File.Exists(xmlPath))
                c.IncludeXmlComments(xmlPath, true);
            else
                _logger.LogWarning($"the '{xmlPath}' not exist.");

            //c.DescribeAllEnumsAsStrings();
            //c.DocumentFilter<ApplyQaTagDescriptions>();
            c.OperationFilter<ApplyDefaultValues>();
            //c.OperationFilter<ApplyUploadFileFilter>();
            //c.SchemaFilter<ApplyModelNameFilter>();

            //classic authentication
            //c.AddSecurityDefinition("Authorization", new ApiKeyScheme { In = "header", Name = "Authorization" });
            
            //oauth2 authentication
            c.OperationFilter<SecurityRequirementsOperationFilter>();
            c.AddSecurityDefinition("oauth2", new OpenApiSecurityScheme
            {
                Name = "Authorization",
                In = ParameterLocation.Header,
                Type = SecuritySchemeType.ApiKey
            });
            // Set the comments path for the Swagger JSON and UI.
            //WebApi xml

        }
    }
}
